
using System.Data;
using System;
using System.IO;
using System.IO.Compression;
using System.Collections;
using System.Collections.Generic;

using System.Web;
using System.Web.UI;
using System.Web.UI.WebControls;
using Microsoft.SharePoint;
using Microsoft.SharePoint.Administration;
using Microsoft.SharePoint.WebControls;
using Microsoft.SharePoint.WebPartPages;
using System.Runtime.Serialization;
using System.Runtime.Serialization.Formatters.Binary;

namespace SharePoint.ImportExport.MigrationSuite
{
    public enum ContentLocationType
    {
        Local,
        UNC
    }
    public enum FormatType
    {
        HTML,
        XML
    }

    /// <summary>
    /// This is the class for storing the info in the configuration database
    /// </summary>
    public class ContentLocation : SPPersistedObject
    {
        [Persisted]
        private ContentLocationType locationType;

        [Persisted]
        private String contentOutputPath;

        [Persisted]
        private String url;

        public ContentLocation()
        { }

        public ContentLocation(string name, SPPersistedObject parent)
            : base(name, parent)
        { ;}

        public override string DisplayName
        {
            get
            {
                return this.Name;
            }
        }

        public String Url
        {
            get { return this.url; }
            set
            {
                if (this.url == value)
                {
                    return;
                }

                this.url = value;

            }
        }

        public ContentLocationType LocationType
        {
            get { return this.locationType; }
            set { this.locationType = value; }
        }

        public String ContentOutputPath
        {
            get { return this.contentOutputPath; }
            set { this.contentOutputPath = value; }
        }
    }

    public class ContentLocationCollection : SPPersistedChildCollection<ContentLocation>
    {
        public ContentLocationCollection(SPPersistedObject parent)
            : base(parent)
        { ;}

        public void Add(String url)
        {
            ContentLocation location = new ContentLocation(String.Empty, this.Parent);

            location.Url = url;

            location.Update();
        }
    }

    public class ExportLocationService : SPService
    {
        [Persisted]

        private static ContentLocationCollection locations;
        private static ExportLocationService local = null;

        /* A static property that retrieves the content service. */
        public static ExportLocationService Local
        {
            get
            {
                if (ExportLocationService.local == null)
                {
                    ExportLocationService.local =
                      SPFarm.Local.Services.GetValue<ExportLocationService>("ExportLocationService");
                }

                return ExportLocationService.local;
            }
        }

        /* A static property for accessing the location collection. */
        public ContentLocationCollection Locations
        {
            get
            {
                if (locations == null)
                {
                    locations = new ContentLocationCollection(this);
                }

                return locations;
            }
        }

        /* An empty public constructor required for serialization. */
        public ExportLocationService()
        { ;}

        public ExportLocationService(SPFarm farm)
            : base("ExportLocationService", farm)
        {/* Add code to initialize as needed. */}

        /* A method to retrieve the content location collection. */
        public ContentLocationCollection GetAllContentLocations()
        {
            ExportLocationService service = ExportLocationService.Local;

            if (service == null)
            {
                return null;
            }

            return service.Locations;
        }

    }
    public partial class MigrationConfiguration : LayoutsPageBase
    {
        // add control fields to match controls tags on .aspx page
        protected TextBox txtDirectories;
        protected TextBox txtSite;
        protected TextBox txtOwner;
        protected TextBox txtEmail;
        protected Label lblStatus;
        protected Button btnSend;
        protected Button btnCreate;

        void btnCreate_Click(Object sender, EventArgs e)
        {
            if (txtSite.Text.Length < 5)
            {
                lblStatus.Text = "You must specify the full URL to the site";
                return;
            }
            if (!txtSite.Text.StartsWith("http"))
            {
                lblStatus.Text = "You must specify the full URL to the site";
                return;
            }
            if (txtOwner.Text.Length < 3)
            {
                lblStatus.Text = "You must specify the owner of the site collection";
                return;
            }
            if (txtEmail.Text.Length < 3)
            {
                lblStatus.Text = "You must specify the email to the owner of the site collection";
                return;
            }

            Button clickedButton = (Button)sender;
            clickedButton.Enabled = false;
            string siteUrl = txtSite.Text;
            Uri uri = new System.Uri(siteUrl);
            SPWebApplication app = SPWebApplication.Lookup(uri);
            if (app != null)
            {
                using (SPLongOperation operation = new SPLongOperation(this.Page))
                {
                    operation.LeadingHTML = "Creating Site";

                    operation.TrailingHTML = "Please wait while the site is being created";

                    operation.Begin();
                    bool listExists = false;
                    Guid exportListID = Guid.Empty;
                    Guid importListID = Guid.Empty;
                    Guid exportViewID = Guid.Empty;
                    Guid importViewID = Guid.Empty;
                    bool found = false;
                    SPSiteCollection siteCollection = app.Sites;
                    string[] sites = siteCollection.Names;
                    foreach (string localsiteUrl in sites)
                    {
                        if (0 == String.Compare(uri.LocalPath, localsiteUrl, true))
                        {
                            found = true;
                            break;
                        }
                    }
                    if (!found)
                    {
                        Microsoft.SharePoint.SPSite site = siteCollection.Add(uri.LocalPath, "Export Import configuration", "This site is used to store migration information", 1033, "STS#1", txtOwner.Text, txtOwner.Text, txtEmail.Text);
                    }

                    using (Microsoft.SharePoint.SPSite site = new Microsoft.SharePoint.SPSite(uri.AbsoluteUri))
                    {
                        using (Microsoft.SharePoint.SPWeb web = site.RootWeb)
                        {
                            foreach (Microsoft.SharePoint.SPList list in web.Lists)
                            {
                                if (list.Title == "ExportedData")
                                {
                                    listExists = true;
                                    exportListID = list.ID;
                                    break;
                                }
                            }

                            if (!listExists)
                            {
                                exportListID = web.Lists.Add("ExportedData", "This contains the export info for the list", SPListTemplateType.GenericList);
                            }

                            if (exportListID != Guid.Empty)
                            {
                                Microsoft.SharePoint.SPList list = web.Lists[exportListID];
                                Microsoft.SharePoint.SPView view = list.DefaultView;
                                exportViewID = view.ID;
                                if (!list.Fields.ContainsField("ExportDirectory"))
                                {
                                    string field = list.Fields.Add("SiteExported", SPFieldType.Text, true);
                                    view.ViewFields.Add(field);

                                    field = list.Fields.Add("ExportDirectory", SPFieldType.Text, true);
                                    view.ViewFields.Add(field);

                                    field = list.Fields.Add("SiteInclusionPath", SPFieldType.Text, true);
                                    view.ViewFields.Add(field);

                                    field = list.Fields.Add("SiteDefinitionName", SPFieldType.Text, true);
                                    view.ViewFields.Add(field);

                                    field = list.Fields.Add("SiteOwner", SPFieldType.Text, false);
                                    view.ViewFields.Add(field);

                                    field = list.Fields.Add("SiteURL", SPFieldType.URL, false);
                                    view.ViewFields.Add(field);

                                    field = list.Fields.Add("Contact", SPFieldType.Text, false);
                                    view.ViewFields.Add(field);

                                    field = list.Fields.Add("IncludeSubSites", SPFieldType.Boolean, true);
                                    view.ViewFields.Add(field);

                                    field = list.Fields.Add("IncludeUserInfo", SPFieldType.Boolean, true);
                                    view.ViewFields.Add(field);

                                    field = list.Fields.Add("ListName", SPFieldType.Text, false);
                                    view.ViewFields.Add(field);

                                    field = list.Fields.Add("FolderName", SPFieldType.Text, false);
                                    view.ViewFields.Add(field);

                                    field = list.Fields.Add("ExportItemsNewerThan", SPFieldType.DateTime, false);
                                    view.ViewFields.Add(field);

                                    field = list.Fields.Add("ExportItemsOlderThan", SPFieldType.DateTime, false);
                                    view.ViewFields.Add(field);

                                    field = list.Fields.Add("IncludeVersions", SPFieldType.Boolean, false);
                                    view.ViewFields.Add(field);
                                    field = list.Fields.Add("Result", SPFieldType.Text, false);
                                    view.Update();
                                }
                            }

                            listExists = false;

                            foreach (Microsoft.SharePoint.SPList list in web.Lists)
                            {
                                if (list.Title == "ImportedData")
                                {
                                    listExists = true;
                                    importListID = list.ID;
                                    break;
                                }

                            }
                            if (!listExists)
                            {
                                importListID = web.Lists.Add("ImportedData", "This contains the import info for the list", SPListTemplateType.GenericList);

                            }
                            if (importListID != Guid.Empty)
                            {
                                Microsoft.SharePoint.SPList list = web.Lists[importListID];
                                Microsoft.SharePoint.SPView view = list.DefaultView;
                                importViewID = view.ID;
                                if (!list.Fields.ContainsField("ImportDirectory"))
                                {
                                    string field = list.Fields.Add("ImportDirectory", SPFieldType.Text, true);
                                    view.ViewFields.Add(field);
                                    field = list.Fields.Add("Result", SPFieldType.Text, false);
                                    view.Update();
                                }
                            }

                            using (Microsoft.SharePoint.WebPartPages.SPLimitedWebPartManager partCollection = web.GetLimitedWebPartManager("default.aspx", System.Web.UI.WebControls.WebParts.PersonalizationScope.Shared))
                            {
                                ListViewWebPart lwp = new ListViewWebPart();
                                lwp.ListName = exportListID.ToString("B").ToUpper();
                                lwp.ViewGuid = exportViewID.ToString("B").ToUpper();
                                lwp.Title = "Exported data";
                                partCollection.AddWebPart(lwp, "Left", 0);
                                partCollection.SaveChanges(lwp);

                                lwp = new ListViewWebPart();
                                lwp.ListName = importListID.ToString("B").ToUpper();
                                lwp.ViewGuid = importViewID.ToString("B").ToUpper();
                                lwp.Title = "Imported data";
                                partCollection.AddWebPart(lwp, "Left", 1);
                                partCollection.SaveChanges(lwp);
                            }
                        }
                    }


                    operation.End(txtSite.Text);
                }
            }
            else
            {
                lblStatus.Text = txtSite.Text + " does not point to a valid Web Application";
            }
        }

        void btnSend_Click(Object sender, EventArgs e)
        {
            Button clickedButton = (Button)sender;
            clickedButton.Enabled = false;

            if (String.IsNullOrEmpty(txtSite.Text))
            {
                lblStatus.Text = "A site must be specified";
                return;
            }

            if (String.IsNullOrEmpty(txtDirectories.Text))
            {
                lblStatus.Text = "The export directories must be specified";
                return;
            }


            btnCreate.Enabled = true;
            ExportLocationService service = ExportLocationService.Local;
            if (service != null)
            {
                Guid g1 = Guid.Empty;
                Guid g2 = Guid.Empty;
                Guid g3 = Guid.Empty;
                Guid g4 = Guid.Empty;

                foreach (ContentLocation loc in service.Locations)
                {
                    if (loc.DisplayName == "MigrationSuite.Directories")
                    {
                        g1 = loc.Id;
                        continue;
                    }

                    if (loc.DisplayName == "MigrationSuite.Site")
                    {
                        g2 = loc.Id;
                        continue;
                    }

                    if (loc.DisplayName == "MigrationSuite.SiteOwner")
                    {
                        g3 = loc.Id;
                        continue;
                    }

                    if (loc.DisplayName == "MigrationSuite.SiteOwnerEmail")
                    {
                        g4 = loc.Id;
                        continue;
                    }
                }

                if (g1 != Guid.Empty)
                {
                    service.Locations.Remove(g1);
                }

                if (g2 != Guid.Empty)
                {
                    service.Locations.Remove(g2);
                }

                if (g3 != Guid.Empty)
                {
                    service.Locations.Remove(g3);
                }

                if (g4 != Guid.Empty)
                {
                    service.Locations.Remove(g4);
                }


            }
            else
            {
                service = new ExportLocationService(SPFarm.Local);
                service.Update();
            }
            ContentLocation locAdd = new ContentLocation("MigrationSuite.Directories", service);
            locAdd.Url = txtDirectories.Text;
            service.Locations.Add(locAdd);
            locAdd = new ContentLocation("MigrationSuite.Site", service);
            locAdd.Url = txtSite.Text;
            service.Locations.Add(locAdd);

            locAdd = new ContentLocation("MigrationSuite.SiteOwner", service);
            locAdd.Url = txtOwner.Text;
            service.Locations.Add(locAdd);

            locAdd = new ContentLocation("MigrationSuite.SiteOwnerEmail", service);
            locAdd.Url = txtEmail.Text;
            service.Locations.Add(locAdd);

        }

        protected override void OnInitComplete(EventArgs e)
        {
            btnSend.Click += new EventHandler(this.btnSend_Click);
            btnCreate.Click += new EventHandler(this.btnCreate_Click);
            btnCreate.Enabled = false;
            try
            {
                if (String.IsNullOrEmpty(txtDirectories.Text))
                {

                    ExportLocationService service = ExportLocationService.Local;
                    if (service != null)
                    {
                        foreach (ContentLocation loc in service.Locations)
                        {
                            if (loc.DisplayName == "MigrationSuite.Directories")
                            {
                                txtDirectories.Text = loc.Url;
                            }
                            if (loc.DisplayName == "MigrationSuite.Site")
                            {
                                txtSite.Text = loc.Url;
                            }
                            if (loc.DisplayName == "MigrationSuite.SiteOwner")
                            {
                                txtOwner.Text = loc.Url;
                            }
                            if (loc.DisplayName == "MigrationSuite.SiteOwnerEmail")
                            {
                                txtEmail.Text = loc.Url;
                            }
                        }

                        lblStatus.Text = "Data read succesfully from the configuration database";
                    }
                }
            }
            catch (Exception Ex)
            {
                lblStatus.Text = Ex.Message;
            }
        }
    }
}
